package main
import (
	"fmt"
	"time"
)
// 示例
func server1(ch chan string) {
	time.Sleep(6 * time.Second)
	ch <- "from server1"
}
func server2(ch chan string) {
	time.Sleep(3 * time.Second)
	ch <- "from server2"
}
func process(ch chan string) {
	time.Sleep(10500 * time.Millisecond)
	ch <- "process successful"
}

// 24. Select select 语句用于在多个发送/接收信道操作中进行选择
// select 语句会一直阻塞，直到发送/接收操作准备就绪。
func main(){
	output1 := make(chan string)
	output2 := make(chan string)
	go server1(output1)
	go server2(output2)
	time.Sleep(1 * time.Second)
	select{			//给用户返回最快的响应了 哪一个快就返回哪一个 并且值返回一个 
	case s1 := <-output1://当 select 由多个 case 准备就绪时，将会随机地选取其中之一去执行。
		fmt.Println(s1)
	case s2 := <-output2:
		fmt.Println(s2)
	}

	// ch := make(chan string)
	// go process(ch)
	// for {
	// 	time.Sleep(1000 * time.Millisecond)
	// 	select {
	// 	case v := <-ch:
	// 		fmt.Println("received value: ", v)
	// 	default:
	// 		fmt.Println("no value received")
	// 	}
	// }

	// 死锁与默认情况 错误
	ch1 := make(chan string)
	select {
	case <-ch1:	//由于没有 Go 协程向该信道写入数据，因此 select 语句会一直阻塞，导致死锁。
	default: //有默认情况就不会死锁 如果 select 只含有值为 nil 的信道，也同样会执行默认情况。
		fmt.Println("default case executed")
	}

	// 空 select 除非有 case 执行，select 语句就会一直阻塞着。在这里，select 语句没有任何 case，因此它会一直阻塞，导致死锁。
	// select {}//错误
}
